/*
 * Copyright (c) Huawei Technologies Co., Ltd. 2021-2021. All rights reserved.
 */

package autodispose;

import io.reactivex.rxjava3.annotations.CheckReturnValue;
import io.reactivex.rxjava3.core.Flowable;
import io.reactivex.rxjava3.disposables.Disposable;
import io.reactivex.rxjava3.functions.Action;
import io.reactivex.rxjava3.functions.Consumer;
import io.reactivex.rxjava3.subscribers.TestSubscriber;
import org.reactivestreams.Subscriber;

/**
 * Subscribe proxy that matches {@link Flowable}'s subscribe overloads.
 *
 * @param <T>
 */
public interface FlowableSubscribeProxy<T> {
    /**
     * Proxy for {@link Flowable#subscribe()}.
     *
     * @return a {@link Disposable}
     */
    Disposable subscribe();

    /**
     * Proxy for {@link Flowable#subscribe(Consumer)}.
     *
     * @param onNext value on next event.
     * @return a {@link Disposable}
     */
    Disposable subscribe(Consumer<? super T> onNext);

    /**
     * Proxy for {@link Flowable#subscribe(Consumer, Consumer)}.
     *
     * @param onNext  value on next event.
     * @param onError value on error.
     * @return a {@link Disposable}
     */
    Disposable subscribe(Consumer<? super T> onNext, Consumer<? super Throwable> onError);

    /**
     * Proxy for {@link Flowable#subscribe(Consumer, Consumer, Action)}.
     *
     * @param onError    value on error.
     * @param onComplete value on competition of events.
     * @param onNext     value on next event.
     * @return a {@link Disposable}
     */
    Disposable subscribe(
            Consumer<? super T> onNext, Consumer<? super Throwable> onError, Action onComplete);

    /**
     * Proxy for {@link Flowable#subscribe(Subscriber)}.
     *
     * @param observer value of subscriber
     */
    void subscribe(Subscriber<? super T> observer);

    /**
     * Proxy for {@link Flowable#subscribeWith(Subscriber)}.
     *
     * @param observer value of subscriber
     * @return an {@link Subscriber}
     */
    @CheckReturnValue
    <E extends Subscriber<? super T>> E subscribeWith(E observer);

    /**
     * Proxy for {@link Flowable#test()}.
     *
     * @return a {@link TestSubscriber}
     */
    @CheckReturnValue
    TestSubscriber<T> test();

    /**
     * Proxy for {@link Flowable#test(long)}.
     *
     * @param initialRequest value of inital value.
     * @return a {@link TestSubscriber}
     */
    @CheckReturnValue
    TestSubscriber<T> test(long initialRequest);

    /**
     * Proxy for {@link Flowable#test(long, boolean)}.
     *
     * @param cancel         true/false to cancel operation or not.
     * @param initialRequest value of inital request.
     * @return a {@link TestSubscriber}
     */
    @CheckReturnValue
    TestSubscriber<T> test(long initialRequest, boolean cancel);
}
